package com.ls.rbac.controller;

import com.ls.rbac.config.Result;
import com.ls.rbac.entity.Permission;
import com.ls.rbac.entity.vo.PermissionVo;
import com.ls.rbac.service.IPermissionService;
import com.ls.rbac.service.IRolePermissionService;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.annotation.Resource;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;
import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.bean.copier.CopyOptions;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;

import java.util.List;

/**
 * @author liusheng
 * @since 2025--06--28
 */
@RestController
@RequestMapping("/permission")
@Tag(name = "权限管理模块", description = " 权限管理相关接口")
public class PermissionController {

    @Resource
    private IPermissionService permissionService;

    @Resource
    private IRolePermissionService rolePermissionService;

    @Operation(summary = "获取菜单树", description = "获取菜单权限树形结构")
    @GetMapping("/tree")
    @PreAuthorize("hasAuthority('sys:menu:list')")
    public Result<List<Permission>> tree() {
        try {
            List<Permission> permissionTree = permissionService.getPermissionTree();
            return Result.success(permissionTree);
        } catch (Exception e) {
            return Result.fail("获取菜单树失败：" + e.getMessage());
        }
    }

    @Operation(summary = "获取菜单列表", description = "获取所有菜单列表（不含树形结构）")
    @GetMapping("/list")
    @PreAuthorize("hasAuthority('sys:menu:list')")
    public Result<List<Permission>> list() {
        try {
            LambdaQueryWrapper<Permission> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.orderByAsc(Permission::getOrderNum);
            List<Permission> permissions = permissionService.list(queryWrapper);
            return Result.success(permissions);
        } catch (Exception e) {
            return Result.fail("获取菜单列表失败：" + e.getMessage());
        }
    }

    @Operation(summary = "添加菜单", description = "新增菜单或按钮权限")
    @PostMapping("/add")
    @PreAuthorize("hasAuthority('sys:menu:add')")
    public Result<Boolean> add(@RequestBody PermissionVo permissionVo) {
        try {
            Permission permission = BeanUtil.copyProperties(permissionVo, Permission.class);
            permission.setDeleted((byte) 0);
            if (permission.getPid() == null || permission.getPid() <= 0) {
                permission.setPid(0);
                permission.setParentLabel("无");
            } else {
                Permission parent = permissionService.getById(permission.getPid());
                if (parent == null) {
                    return Result.fail("上级部门不存在");
                }
                permission.setParentLabel(parent.getPermissionLabel());
            }
            boolean success = permissionService.save(permission);
            return success ? Result.success(true, "添加成功") : Result.fail("添加失败");
        } catch (Exception e) {
            return Result.fail("添加菜单失败：" + e.getMessage());
        }
    }

    @Operation(summary = "获取菜单详情", description = "根据ID获取菜单详情")
    @GetMapping("/{id}")
    @PreAuthorize("hasAuthority('sys:menu:list')")
    public Result<Permission> getById(@Parameter(description = "菜单ID") @PathVariable Integer id) {
        try {
            Permission permission = permissionService.getById(id);
            if (permission == null) {
                return Result.fail("菜单不存在");
            }
            return Result.success(permission);
        } catch (Exception e) {
            return Result.fail("获取菜单详情失败：" + e.getMessage());
        }
    }

    @Operation(summary = "更新菜单", description = "修改菜单或按钮权限信息")
    @PutMapping("/update")
    @PreAuthorize("hasAuthority('sys:menu:edit')")
    public Result<Boolean> update(@RequestBody PermissionVo permissionVo) {
        try {
            if (permissionVo.getId() == null) {
                return Result.fail("菜单ID不能为空");
            }
            Permission permission = permissionService.getById(permissionVo.getId());
            BeanUtil.copyProperties(permissionVo, permission, CopyOptions.create().ignoreNullValue());
            Permission parent = permissionService.getById(permission.getPid());
            permission.setParentLabel(parent.getPermissionLabel());
            boolean success = permissionService.updateById(permission);
            return success ? Result.success(true, "更新成功") : Result.fail("更新失败");
        } catch (Exception e) {
            return Result.fail("更新菜单失败：" + e.getMessage());
        }
    }

    @Operation(summary = "删除菜单", description = "根据ID删除菜单")
    @DeleteMapping("/{id}")
    @PreAuthorize("hasAuthority('sys:menu:delete')")
    public Result<Boolean> delete(@Parameter(description = "菜单ID") @PathVariable Integer id) {
        try {
            List<Permission> children = permissionService.list(
                    new LambdaQueryWrapper<Permission>()
                            .eq(Permission::getPid, id)
            );
            if (!children.isEmpty()) {
                return Result.fail("该菜单下存在子菜单，请先删除子菜单");
            }
            permissionService.deletePermissionAndRolePermission(id);
            return Result.success(true, "删除成功");
        } catch (Exception e) {
            return Result.fail("删除菜单失败：" + e.getMessage());
        }
    }

    @Operation(summary = "获取父级菜单(用于新增)", description = "获取所有可作为父级的菜单,用于新增,不包含按钮权限")
    @GetMapping("/parentsNew")
    @PreAuthorize("hasAuthority('sys:menu:list')")
    public Result<List<Permission>> getParentMenus() {
        try {
            LambdaQueryWrapper<Permission> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.in(Permission::getPermissionType, 0, 1)
                    .orderByAsc(Permission::getOrderNum);
            List<Permission> parentMenus = permissionService.list(queryWrapper);
            List<Permission> permissionTreeParent = permissionService.getPermissionTreeParent(parentMenus);
            return Result.success(permissionTreeParent);
        } catch (Exception e) {
            return Result.fail("获取父级菜单失败：" + e.getMessage());
        }
    }


    @Operation(summary = "获取父级菜单（用于修改）", description = "获取所有可作为父级的菜单,用于修改,排除当前菜单及其子菜单,不包含按钮权限")
    @GetMapping("/parentsModify")
    @PreAuthorize("hasAuthority('sys:menu:list')")
    public Result<List<Permission>> getParentMenusModify(@RequestParam(required = false) Integer excludeId) {
        try {
            LambdaQueryWrapper<Permission> queryWrapper = new LambdaQueryWrapper<>();
            if (excludeId != null && excludeId > 0) {
                List<Integer> excludeIds = permissionService.getPermissionAndChildrenIds(excludeId);
                if (!excludeIds.isEmpty()) {
                    queryWrapper.notIn(Permission::getId, excludeIds);
                }
            }
            queryWrapper.in(Permission::getPermissionType, 0, 1)
                    .orderByAsc(Permission::getOrderNum);
            List<Permission> parentMenus = permissionService.list(queryWrapper);
            List<Permission> permissionTreeParent = permissionService.getPermissionTreeParent(parentMenus);
            return Result.success(permissionTreeParent);
        } catch (Exception e) {
            return Result.fail("获取父级菜单失败：" + e.getMessage());
        }
    }
}
